﻿using System;
using System.Collections.Generic;
using System.Globalization;
using System.Linq;
using EstateNuke.Data.Properties;

namespace EstateNuke.Data
{
    public partial class Report
    {
        #region Fileds & Properties

        /// <summary>
        /// </summary>
        public string DisplayName
        {
            get
            {
                return string.Format("{0}-{1}{2}", BeginDate.ToString("yyyy年MM月dd日"), EndDate.ToString("yyyy年MM月dd日"), IsDeleted ? " (已删除)" : "");
            }
        }

        /// <summary>
        /// </summary>
        public bool HasReportAttachments
        {
            get
            {
                return InternalReportAttachments.Any(reportAttachment => reportAttachment.IsDeleted == false);
            }
        }

        /// <summary>
        /// </summary>
        public IList<ReportAttachment> ReportAttachments
        {
            get
            {
                return InternalReportAttachments.Where(reportAttachment => reportAttachment.IsDeleted == false).ToList();
            }
        }

        /// <summary>
        /// </summary>
        public IList<ReportReply> ReportReplies
        {
            get
            {
                return InternalReportReplies.Where(reportReply => reportReply.IsDeleted == false).ToList();
            }
        }

        #endregion

        #region Add & Remove ReportAttachment

        /// <summary>
        /// </summary>
        /// <returns></returns>
        public ReportAttachment AddReportAttachment(User modifiedUser)
        {
            if (modifiedUser == null)
            {
                throw new ArgumentNullException("modifiedUser");
            }
            var reportAttachment = new ReportAttachment
                                       {
                                           RowId = Guid.NewGuid(),
                                           CreatedDate = DateTime.Now,
                                       };
            InternalReportAttachments.Add(reportAttachment);
            reportAttachment.IsDeleted = false;
            reportAttachment.ModifiedDate = DateTime.Now;
            reportAttachment.ModifiedByUser = modifiedUser;
            return reportAttachment;
        }

        /// <summary>
        /// </summary>
        /// <param name = "name"></param>
        /// <param name = "modifiedUser"></param>
        /// <returns></returns>
        public ReportAttachment AddReportAttachment(string name, User modifiedUser)
        {
            if (string.IsNullOrEmpty(name))
            {
                throw new ArgumentNullException("name");
            }
            if (modifiedUser == null)
            {
                throw new ArgumentNullException("modifiedUser");
            }
            if (InternalReportAttachments.Any(item => item.IsDeleted == false && item.Name == name))
            {
                throw new InvalidOperationException(string.Format(CultureInfo.CurrentCulture, Resources.DuplicatedReportAttachment, name));
            }
            var reportAttachment = InternalReportAttachments.FirstOrDefault(item => item.IsDeleted && item.Name == name);
            if (reportAttachment == null)
            {
                reportAttachment = new ReportAttachment
                                       {
                                           RowId = Guid.NewGuid(),
                                           CreatedDate = DateTime.Now,
                                       };
                InternalReportAttachments.Add(reportAttachment);
            }
            reportAttachment.IsDeleted = false;
            reportAttachment.ModifiedDate = DateTime.Now;
            reportAttachment.ModifiedByUser = modifiedUser;
            reportAttachment.Name = name;
            return reportAttachment;
        }

        /// <summary>
        /// </summary>
        /// <param name = "reportAttachment"></param>
        /// <param name = "modifiedUser"></param>
        public void RemoveReportAttachment(ReportAttachment reportAttachment, User modifiedUser)
        {
            if (reportAttachment == null)
            {
                throw new ArgumentNullException("reportAttachment");
            }
            if (modifiedUser == null)
            {
                throw new ArgumentNullException("modifiedUser");
            }
            if (InternalReportAttachments.Contains(reportAttachment))
            {
                reportAttachment.Delete(modifiedUser);
            }
        }

        #endregion

        #region Add & Remove ReportReply

        /// <summary>
        /// </summary>
        /// <returns></returns>
        public ReportReply AddReportReply(User modifiedUser)
        {
            if (modifiedUser == null)
            {
                throw new ArgumentNullException("modifiedUser");
            }
            var reportReply = new ReportReply
                                  {
                                      RowId = Guid.NewGuid(),
                                      CreatedDate = DateTime.Now,
                                  };
            InternalReportReplies.Add(reportReply);
            reportReply.IsDeleted = false;
            reportReply.ModifiedDate = DateTime.Now;
            reportReply.ModifiedByUser = modifiedUser;
            reportReply.RepliedByUser = modifiedUser;
            reportReply.RepliedDate = DateTime.Now;
            return reportReply;
        }

        /// <summary>
        /// </summary>
        /// <param name = "reportReply"></param>
        /// <param name = "modifiedUser"></param>
        public void RemoveReportReply(ReportReply reportReply, User modifiedUser)
        {
            if (reportReply == null)
            {
                throw new ArgumentNullException("reportReply");
            }
            if (modifiedUser == null)
            {
                throw new ArgumentNullException("modifiedUser");
            }
            if (InternalReportReplies.Contains(reportReply))
            {
                reportReply.Delete(modifiedUser);
            }
        }

        #endregion

        #region Ensure

        /// <summary>
        /// </summary>
        public void Ensure()
        {
        }

        #endregion

        #region Delete

        /// <summary>
        /// </summary>
        public void Delete(User modifiedUser)
        {
            if (modifiedUser == null)
            {
                throw new ArgumentNullException("modifiedUser");
            }
            IsDeleted = true;
            ModifiedDate = DateTime.Now;
            ModifiedByUser = modifiedUser;
            ((List<ReportAttachment>) ReportAttachments).ForEach(reportAttachment => reportAttachment.Delete(modifiedUser));
            ((List<ReportReply>) ReportReplies).ForEach(reportReply => reportReply.Delete(modifiedUser));
        }

        /// <summary>
        /// </summary>
        public void CancelDelete(User modifiedUser)
        {
            if (modifiedUser == null)
            {
                throw new ArgumentNullException("modifiedUser");
            }
            IsDeleted = false;
            ModifiedDate = DateTime.Now;
            ModifiedByUser = modifiedUser;
        }

        #endregion
    }
}